package com.smartcruise.util.network;

import android.util.Log;

import com.smartcruise.MyApplication;
import com.smartcruise.data.ReportData;
import com.smartcruise.data.cruiseData.CruiseContract;
import com.smartcruise.data.cruiseData.CruiseData;
import com.smartcruise.util.Key;
import com.smartcruise.util.network.callBack.BaseCallBack;
import com.smartcruise.util.network.netUtils.NetStatusUtils;
import com.smartcruise.util.network.netUtils.Result;

import io.realm.Realm;
import io.realm.RealmResults;

/**
 * Created by FengChaoQun
 * on 2018/3/6 0006
 * 自动上传数据
 */

public class DataAutoUpload {

    private boolean isUploading;//正在上传
    private Realm realm = MyApplication.getInstance().getRealm();

    private DataAutoUpload() {

    }

    static class InstanceHolder {
        final static DataAutoUpload instance = new DataAutoUpload();
    }

    public static DataAutoUpload getInstance() {
        return InstanceHolder.instance;
    }

    public synchronized void start() {
        if (NetStatusUtils.isConnected(MyApplication.getInstance()) && NetStatusUtils.isWifi(MyApplication.getInstance()) && !isUploading) {
            checkData();
        }
    }

    public synchronized void destroy() {
        realm.close();
    }

    private synchronized void checkData() {
        //找到一个已完成的但是未全部上传的本地任务
        CruiseData localData = realm.where(CruiseData.class)
                .equalTo(Key.isCopyData, true)
                .equalTo(Key.statusInApp, CruiseContract.TASK_IS_END)
                .not().equalTo(Key.uploadStatus, 2)
                .findFirst();

        if (localData != null) {
            uploadCruiseData(localData, realm);
            return;
        }

        //找到一个经修改过但是还未上传完成的从服务器拉取的任务
        CruiseData failData = realm.where(CruiseData.class)
                .equalTo(Key.isFromNet, true)
                .equalTo(Key.dataChanged, true)
                .not().equalTo(Key.uploadStatus, 2)
                .findFirst();
        if (failData != null) {
            uploadCruiseData(failData, realm);
            return;
        }

        //找到一个本地的未全部上传的通报
        RealmResults<ReportData> reportDataRealmResults = realm.where(ReportData.class)
                .equalTo(Key.isFromNet, false)
                .not().equalTo(Key.uploadStatus, 2)
                .findAll();
        for (ReportData reportDataRealmResult : reportDataRealmResults) {
            if (reportDataRealmResult.checkLocalContent()) {//只有内容齐全的通报才可以上传
                uploadReportData(reportDataRealmResult, realm);
                return;
            }
        }

        //找到一个修改过的已上传的通报
        ReportData netData = realm.where(ReportData.class)
                .equalTo(Key.isFromNet, true)
                .equalTo(Key.dataChanged, true)
                .not().equalTo(Key.uploadStatus, 2)
                .findFirst();
        if (netData != null) {
            uploadReportData(netData, realm);
            return;
        }

    }

    private synchronized void uploadCruiseData(CruiseData cruiseData, Realm realm) {
        Log.d("DataAutoUpload", "自动上传数据--开始");
        TaskUploadBack taskUploadBack = new TaskUploadBack(cruiseData, realm);
        isUploading = true;
        taskUploadBack.uploadAll(new BaseCallBack() {
            @Override
            public void onSuccess(Result result) {
                isUploading = false;
                Log.d("DataAutoUpload", "自动上传数据--成功");
                start();
            }

            @Override
            public void onFail(Result result) {
                isUploading = false;
                Log.e("DataAutoUpload", "自动上传数据--失败");
            }

            @Override
            public void onError(Throwable e) {
                isUploading = false;
                Log.e("DataAutoUpload", "自动上传数据--异常");
                e.printStackTrace();
            }
        });
    }

    private synchronized void uploadReportData(ReportData reportData, Realm realm) {
        Log.d("DataAutoUpload", "自动上传通报--开始");
        ReportUploadBack reportUploadBack = new ReportUploadBack(realm, reportData);
        isUploading = true;
        reportUploadBack.uploadOneNodeAllData(new BaseCallBack() {
            @Override
            public void onSuccess(Result result) {
                isUploading = false;
                Log.d("DataAutoUpload", "自动上传通报--成功");
                start();
            }

            @Override
            public void onFail(Result result) {
                isUploading = false;
                Log.e("DataAutoUpload", "自动上传通报--失败");
            }

            @Override
            public void onError(Throwable e) {
                isUploading = false;
                Log.e("DataAutoUpload", "自动上传通报--异常");
                e.printStackTrace();
            }
        });
    }

}
